package com.zhq.apputil.widget;

import android.content.Context;
import android.content.res.TypedArray;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.os.Build;
import android.util.AttributeSet;
import android.view.View;

import com.zhq.apputil.R;
import com.zhq.apputil.utils.ScreenUtils;

import androidx.annotation.ColorInt;
import androidx.annotation.Nullable;

/**
 * @author ZHQ
 * @create 2020/1/16
 * @Describe
 */
public class CircleProgressBar extends View {

    private int mBorderColor;        //边框颜色
    private float mBorderWidth;      //边框宽度
    private int mProgressColor;      //进度颜色
    private float mMargin;           //进度与边框间距
    private int mMax;                //总进度
    private int mProgress;           //当前进度

    private int mDefaultBorderWidth; //默认边框宽度
    private int mDefaultMargin;      //默认进度与边框间距

    private Paint mStrokePaint, mProgressPaint;   //画笔
    private float mRadius;    //半径

    public CircleProgressBar(Context context) {
        this(context, null);
    }

    public CircleProgressBar(Context context, @Nullable AttributeSet attrs) {
        this(context, attrs, 0);
    }

    public CircleProgressBar(Context context, @Nullable AttributeSet attrs, int defStyleAttr) {
        super(context, attrs, defStyleAttr);
        initPaint();
        initAttrs(context, attrs);
    }

    private void initAttrs(Context context, @Nullable AttributeSet attrs) {
        TypedArray ta = context.obtainStyledAttributes(attrs, R.styleable.CircleProgressBar);

        mBorderColor = ta.getColor(R.styleable.CircleProgressBar_cpb_border_color, Color.WHITE);
        setBorderColor(mBorderColor);

        mDefaultBorderWidth = ScreenUtils.dpToPx(context.getResources(), 1);
        mBorderWidth = ta.getDimension(R.styleable.CircleProgressBar_cpb_border_width, mDefaultBorderWidth);
        setBorderWidth(mBorderWidth);

        mProgressColor = ta.getColor(R.styleable.CircleProgressBar_cpb_progress_color, Color.WHITE);
        setProgressColor(mProgressColor);

        mDefaultMargin =  ScreenUtils.dpToPx(context.getResources(), 2);
        mMargin = ta.getDimension(R.styleable.CircleProgressBar_cpb_margin, mDefaultMargin);
        setMargin(mMargin);

        int defaultMax = 100;
        mMax = ta.getInt(R.styleable.CircleProgressBar_cpb_max, defaultMax);
        setMax(mMax);

        int defaultProgress = 0;
        mProgress = ta.getInt(R.styleable.CircleProgressBar_cpb_progress, defaultProgress);
        setProgress(mProgress);

        ta.recycle();
    }

    /**
     * 初始化画笔
     */
    private void initPaint() {
        //边框画笔
        mStrokePaint = new Paint();
        mStrokePaint.setAntiAlias(true);
        mStrokePaint.setStyle(Paint.Style.STROKE);
        mStrokePaint.setStrokeWidth(mBorderWidth);
        mStrokePaint.setColor(mBorderColor);
        //进度画笔
        mProgressPaint = new Paint();
        mProgressPaint.setAntiAlias(true);
        mProgressPaint.setStyle(Paint.Style.FILL);
        mProgressPaint.setColor(mProgressColor);
    }

    @Override
    protected void onSizeChanged(int w, int h, int oldw, int oldh) {
        super.onSizeChanged(w, h, oldw, oldh);
        int width = w - getPaddingLeft() - getPaddingRight();
        int height = h - getPaddingTop() - getPaddingBottom();
        //取宽高最小值一半作为半径
        mRadius = Math.min(width, height) * 1.0f / 2;
    }

    @Override
    protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
        super.onMeasure(widthMeasureSpec, heightMeasureSpec);
        //处理wrap_content情况
        int widthSize = MeasureSpec.getSize(widthMeasureSpec);
        int widthMode = MeasureSpec.getMode(widthMeasureSpec);
        int heightSize = MeasureSpec.getSize(heightMeasureSpec);
        int heightMode = MeasureSpec.getMode(heightMeasureSpec);
        //默认大小
        int defaultSize =  ScreenUtils.dpToPx(getContext().getResources(), 100);
        if (widthMode == MeasureSpec.AT_MOST && heightMode == MeasureSpec.AT_MOST) {
            setMeasuredDimension(defaultSize, defaultSize);
        } else if (widthMode == MeasureSpec.AT_MOST) {
            setMeasuredDimension(defaultSize, heightSize);
        } else if (heightMode == MeasureSpec.AT_MOST) {
            setMeasuredDimension(widthSize, defaultSize);
        }
    }

    @Override
    protected void onDraw(Canvas canvas) {
        //画布透明
        canvas.drawColor(Color.TRANSPARENT);
        //绘制边框
        canvas.drawCircle(mRadius, mRadius, mRadius - mBorderWidth / 2, mStrokePaint);
        //绘制进度
        if (mProgress >= 0 && mMax > 0 && mProgress <= mMax) {
            float percent = mProgress * 1.0f / mMax;
            if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
                canvas.drawArc(mBorderWidth + mMargin, mBorderWidth + mMargin, mRadius * 2 - mBorderWidth - mMargin,
                        mRadius * 2 - mBorderWidth - mMargin, -90, 360 * percent, true, mProgressPaint);
            }
        }
    }

    /**
     * 设置边框颜色
     */
    public void setBorderColor(@ColorInt int borderColor) {
        mStrokePaint.setColor(borderColor);
        postInvalidate();
    }

    /**
     * 设置边框宽度
     */
    public void setBorderWidth(float borderWidth) {
        mBorderWidth = borderWidth;
        if (mBorderWidth < 0) {
            mBorderWidth = mDefaultBorderWidth;
        }
        mStrokePaint.setStrokeWidth(mBorderWidth);
        postInvalidate();
    }

    /**
     * 设置进度颜色
     */
    public void setProgressColor(@ColorInt int progressColor) {
        mProgressPaint.setColor(progressColor);
        postInvalidate();
    }

    /**
     * 设置进度与边框间距
     */
    public void setMargin(float margin) {
        mMargin = margin;
        if (mMargin < 0) {
            mMargin = mDefaultMargin;
        }
        postInvalidate();
    }

    /**
     * 设置进度最大值
     */
    public synchronized void setMax(int max) {
        mMax = max;
        if (mMax > 0) {
            postInvalidate();
        }
    }

    /**
     * 获取进度最大值
     */
    public synchronized int getMax() {
        return mMax;
    }

    /**
     * 设置当前进度
     */
    public synchronized void setProgress(int progress) {
        mProgress = progress;
        if (mProgress >= 0) {
            //当前进度超过总进度，不再绘制
            if (mProgress > mMax) {
                mProgress = mMax;
                return;
            }
            postInvalidate();
        }
    }

    /**
     * 获取当前进度
     */
    public synchronized int getProgress() {
        return mProgress;
    }
}
